<?php

// Diese Klasse erzeugt EINE Ziffer
class WSB_Captcha_Number_Digit
{

  // Die Zweierpotenzen sind hier schon berechnet notiert, damit sie nicht jedes Mal neu
  // ausgerechnet werden muessen. Wir benoetigen fuer eine 5x3-Matrix, deren Zellen mit
  // Zweierpotenzen maskiert sein sollen 15 Bits, also die Bitmasken 2^0 bis 2^14
  var $bits = array(1,2,4,8,16,32,64,128,256,512,1024,2048,4096,8192,16384);

  // Dieses Array enthaelt die Zeilen einer Ziffer, deren Zellen wiederum als Array dargestellt werden
  // Siehe Konstruktor
  var $matrix  = array();

  // Dies sind die fertig berechneten Bitmasken der Ziffern 0 bis 9 in Dezimaldarstellung
  var $bitmasks = array(31599, 18740, 29607, 31143, 18921, 31183, 31695, 18855, 31727, 31215);

  // Konstruktor; nimmt die darzustellende Ziffern entgegen; Matrix wird initialisiert
  // setMatrix() wird mit der korrekten Bitmaske der darzustellenden Ziffer aufgeruefen
  function __construct( $dig )
	{
    $this->matrix[] = array(0, 0, 0); // 2^0, 2^1, 2^2 ... usw.
    $this->matrix[] = array(0, 0, 0);
    $this->matrix[] = array(0, 0, 0);
    $this->matrix[] = array(0, 0, 0);
    $this->matrix[] = array(0, 0, 0); // ..., ..., 2^14

    ((int)$dig >= 0 && (int)$dig <= 9) && $this->setMatrix( $this->bitmasks[(int)$dig] );
  }

  // Methode erzeugt anhand der Bitmaske die Matrix der Ziffer
  // Vom Konstruktor erhaelt die Methode die Bitmaske der darzustellenden Ziffer
  function setMatrix( $bitmask )
	{
    $bitsset = array();

    // Jetzt wird jedes Bit daraufhin geprueft, ob es zur Bitmaske gehoert
    // Wenn ja, wird es im Array $bitset gespeichert
    for ($i=0; $i<count($this->bits); ++$i)
      (($bitmask & $this->bits[$i]) != 0) && $bitsset[] = $this->bits[$i];

    // Nun wird die initialisierte und leere Matrix hergenommen und Zeile fuer Zeile und Zelle fuer Zelle
    // bestueckt. Zellen, die leer sein sollen, bleiben auf 0, aktivierte Zellen erhalten den Wert 1
    // Beispiel aus dem Konstruktor - die Ziffer 1 wuerde als Matrix so aussehen:
    //     $this->matrix[] = array(0, 0, 1); // 2^0, 2^1, 2^2 ... usw.
    //     $this->matrix[] = array(0, 1, 1);
    //     $this->matrix[] = array(0, 0, 1);
    //     $this->matrix[] = array(0, 0, 1);
    //     $this->matrix[] = array(0, 0, 1); // ..., ..., 2^14
    foreach($this->matrix AS $row=>$col)
      foreach($col AS $cellnr => $bit)
        in_array( pow(2,($row*3+$cellnr)), $bitsset) && $this->matrix[$row][$cellnr] = 1;
  }
}